/*
 * Copyright 2009 Google Inc.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package simple.runtime;

import java.lang.reflect.Array;
import java.util.HashSet;
import java.util.Set;

import simple.runtime.annotations.SimpleFunction;
import simple.runtime.annotations.SimpleObject;
import simple.runtime.variants.Variant;

/**
 * 实现各种阵列相关的运行时函数。
 * 
 * @author Herbert Czymontek
 */
@SimpleObject
public final class 数组 {

  private 数组() {  // COV_NF_LINE
  }                   // COV_NF_LINE

  /**
   * 过滤数组的文本内容。
   * 
   * @param array  要搜索的数组
   * @param str  要在数组中搜索的子文本
   * @param include  如果{@code true}则在结果中包含匹配的子文本，否则排除它们
   * @return  包含（非）匹配数组项的数组
   */
  @SimpleFunction
  public static String[] 过滤数组文本(String[] array, String str, boolean include) {
    if (str == null) {
      throw new NullPointerException();
    }

    Set<String> result = new HashSet<String>();
    for (String a : array) {
      if (a.contains(str) == include) {
        result.add(a);
      }
    }
    return result.toArray(new String[result.size()]);
  }

  /**
   * 将数组成员追加到单个文本中。
   * 
   * @param array  包含要连接文本的数组
   * @param separator  在数组成员之间连接文本
   * @return  包含连接数组成员的文本
   */
  @SimpleFunction
  public static String 连接数组文本(String[] array, String separator) {
    if (separator == null) {
      throw new NullPointerException();
    }

    StringBuilder sb = new StringBuilder();
    String sep = "";
    for (String a : array) {
     sb.append(sep).append(a);
     sep = separator;
    }
    return sb.toString();
  }

  /**
   * 查找指定文本来分割文本。
   * 
   * @param str  欲分割的文本
   * @param separator  欲查找的分割文本
   * @param count  分割次数
   * @return  包含分割后的文本数组
   */
  @SimpleFunction
  public static String[] 分割文本(String str, String separator, int count) {
    if (separator == null) {
      throw new NullPointerException();
    }

    if (count <= 0) {
      throw new IllegalArgumentException("Count for Split() out of range. Should greater than 0.");
    }

    return str.split("\\Q" + separator + "\\E", count);
  }

  /**
   * 返回数组维度的大小。
   * 
   * @param array  请求其大小的数组
   * @param dim  维度（第一个维度为1，依此类推）
   * @return  数组维度的大小
   */
  @SimpleFunction
  public static int 取数组下标(Variant array, int dim) {
    if (dim <= 0) {
      throw new IllegalArgumentException("Dimension for UBound() out of range. " +
          "Should be greater than 0.");
    }

    Object arr = array.getArray();
    while (--dim > 0) {
      arr = Array.get(arr, 0);
    }

    return Array.getLength(arr);
  }

  /** 扩展 **/
  
  /**
   * 取数组第一个维度的成员数。
   * 
   * @param array 欲取成员的数组。
   * @return 数组维度的大小
   */
  @SimpleFunction
  public static int 取数组成员数(Variant array) {
    return 取数组下标(array, 1);
  }
}
